package com.example.demo.concurrent;/**
 * Created by kete on 2019-04-10.
 */

/**
 * 作者：kete
 * 创建时间：2019-04-10 15:16
 * 功能描述：
 * 版本：
 */
public class ArrayQueue<T> {

    private int count = 0;

    private Object[] items;

    private Object writeLock;

    private Object readLock;

    private int putIndex;

    private int getIndex;

    public ArrayQueue(int size) {

        items = new Object[size];
        writeLock = new Object();
        readLock = new Object();
        putIndex = 0;
        getIndex = 0;
    }

    public int size(){
        synchronized (readLock) {
            return count;
        }
    }

    public boolean isEmpty(){

        synchronized (readLock){

            return count == 0;
        }
    }

    public T get(){

        synchronized (readLock){
            while(0 == count){

                try {
                    readLock.wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                    break;
                }

            }
        }

        synchronized (writeLock){

            Object result = items[getIndex];
            items[getIndex] = null;
            count--;
            getIndex++;

            if(getIndex == items.length){
                getIndex = 0;
            }

            writeLock.notify();

            return (T)result;
        }

    }

    public void put(T t){

        synchronized (writeLock){
            while(items.length == count){
                try {
                    writeLock.wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                    break;
                }
            }
        }

        synchronized (readLock){
            items[putIndex] = t;
            count++;

            putIndex++;
            if(putIndex == items.length){
                putIndex =0;
            }

            readLock.notify();
        }

    }
}
